--- Example with references
module examples.RefExample where

import frege.Prelude hiding (STMutable, pure)

type Var a b = Mutable a (Ref b)

newVar :: v -> ST st (Var st v)
newVar a = Ref.new a

getVar :: (Var st v) -> ST st v
getVar r = Ref.get r

putVar :: (Var st v) -> v -> ST st ()
putVar r a = Ref.put r a

--- increment the referenced value
incVar ref = do
    int <- getVar ref
    putVar ref (int+1)

workVar n = do
    ref     <- newVar n             -- create a Int reference
    incVar ref                      -- increment 3 times
    inc1 <- getVar ref              -- remember value after first increment
    incVar ref
    incVar ref
    inc3 <- getVar ref              -- get the final value
    ST.return (inc1, inc3)          -- make ST s (Int, Int)
    
foo = workVar 42
bar = ST.run foo -- (workVar 42)
pure n = ST.run (workVar n)
standaloneVal = newVar 0    

main _ = println (ST.run foo)
-- nogo1 :: Var µ Int
-- nogo1 = ST.run standaloneVal
    
-- nogo2 = ST.run (incVar (newVar 0))
